// compile: g++ -o forward forward.cc -std=c++11
// run: ./forward
#include <iostream>

using namespace std;

void Func(int& i) { cout << "lvalue" << endl; }
void Func(const int& i) { cout << "lvalue" << endl; }
void Func(int&& i) { cout << "rvalue" << endl; }

// Forward1参数传递触发拷贝，效率不好
template <typename T>
void Forward1(T i) {
  Func(i);
}
// Forward2无法接受右值参数
template <typename T>
void Forward2(T& i) {
  Func(i);
}
// Forward3能够接受左值和右值，但由于const的限制，无法修改值
template <typename T>
void Forward3(const T& i) {
  // i是有名字的变量，为一个左值
  Func(i);
}
// 注意:在Forward1、Forward2、Forward3函数中变量i为一个左值变量!
// 完美转发
template <typename T>
void Perfect_Forward1(T&& i) {
  Func(std::forward<T>(i));
  // Func(static_cast<T&&>(i));  // 这行代码与上等价
}

void Test1() {
  int a = 0;
  Func(a);
  Func(0);
  cout << "-------forward1--------" << endl;
  Forward1(a);
  Forward1(0);
  cout << "-------forward2--------" << endl;
  // Forward2(0); 编译错误，传入参数必须为左值
  Forward2(a);
  cout << "-------forward3--------" << endl;
  Forward3(a);
  Forward3(0);
  cout << "-------Perfect_Forward1--------" << endl;
  Perfect_Forward1(a);
  Perfect_Forward1(0);
}
int main() {
  Test1();
  return 0;
}